# encoding:utf-8

import cv2
import cvui
import numpy as np

WINDOWS_TITLE = "Tic Tac Toe"

SCORE_00 = 1
SCORE_1_01 = 3
SCORE_1_02 = 2
SCORE_2_01 = 2
SCORE_2_02 = 3
SCORE_12 = 0
SCORE_1_11 = 50
SCORE_1_22 = 40
SCORE_2_11 = 40
SCORE_2_22 = 50

cell = [0, 0, 0,
        0, 0, 0,
        0, 0, 0]  # 0 for no use, 1 for player 1, 2 for player 2

firstHand = True

WIN_WAY_0 = [[1, 2], [3, 6], [4, 8]]
WIN_WAY_1 = [[0, 2], [4, 7]]
WIN_WAY_2 = [[0, 1], [5, 8], [4, 6]]
WIN_WAY_3 = [[0, 6], [4, 5]]
WIN_WAY_4 = [[0, 8], [1, 7], [2, 6], [3, 5]]
WIN_WAY_5 = [[3, 4], [2, 8]]
WIN_WAY_6 = [[0, 3], [2, 4], [7, 8]]
WIN_WAY_7 = [[1, 4], [6, 8]]
WIN_WAY_8 = [[0, 4], [2, 5], [6, 7]]

WIN_WAY = [WIN_WAY_0, WIN_WAY_1, WIN_WAY_2,
           WIN_WAY_3, WIN_WAY_4, WIN_WAY_5,
           WIN_WAY_6, WIN_WAY_7, WIN_WAY_8]


# 初始化函数
def Init():
    cell = [0, 0, 0,
            0, 0, 0,
            0, 0, 0]


# 平局监测
def DrawCheck():
    for x in cell:
        if x == 0:
            return 0
    return 1


# 获胜检测
def WinCheck():
    winFlag = 0
    if cell[0] == cell[1] == cell[2] == 1:
        winFlag = 1
    if cell[0] == cell[3] == cell[6] == 1:
        winFlag = 1
    if cell[0] == cell[4] == cell[8] == 1:
        winFlag = 1
    if cell[1] == cell[4] == cell[7] == 1:
        winFlag = 1
    if cell[2] == cell[5] == cell[8] == 1:
        winFlag = 1
    if cell[2] == cell[4] == cell[6] == 1:
        winFlag = 1
    if cell[3] == cell[4] == cell[5] == 1:
        winFlag = 1
    if cell[6] == cell[7] == cell[8] == 1:
        winFlag = 1

    if cell[0] == cell[1] == cell[2] == 2:
        winFlag = 2
    if cell[0] == cell[3] == cell[6] == 2:
        winFlag = 2
    if cell[0] == cell[4] == cell[8] == 2:
        winFlag = 2
    if cell[1] == cell[4] == cell[7] == 2:
        winFlag = 2
    if cell[2] == cell[5] == cell[8] == 2:
        winFlag = 2
    if cell[2] == cell[4] == cell[6] == 2:
        winFlag = 2
    if cell[3] == cell[4] == cell[5] == 2:
        winFlag = 2
    if cell[6] == cell[7] == cell[8] == 2:
        winFlag = 2

    return winFlag


def CalculatingScore():
    score = [0, 0, 0,
             0, 0, 0,
             0, 0, 0]

    if not firstHand:
        SCORE_01 = SCORE_1_01
        SCORE_02 = SCORE_1_02
        SCORE_11 = SCORE_1_11
        SCORE_22 = SCORE_1_22
    else:
        SCORE_01 = SCORE_2_01
        SCORE_02 = SCORE_2_02
        SCORE_11 = SCORE_2_11
        SCORE_22 = SCORE_2_22

    for x in range(0, 9):
        if cell[x] == 0:
            for y in WIN_WAY[x]:
                if cell[y[0]] + cell[y[1]] == 0:
                    score[x] += SCORE_00
                if cell[y[0]] + cell[y[1]] == 1:
                    score[x] += SCORE_01
                if cell[y[0]] + cell[y[1]] == 2 and cell[y[0]] * cell[y[1]] == 0:
                    score[x] += SCORE_02
                if cell[y[0]] + cell[y[1]] == 2 and cell[y[0]] * cell[y[1]] == 1:
                    score[x] += SCORE_11
                if cell[y[0]] + cell[y[1]] == 3:
                    score[x] += SCORE_12
                if cell[y[0]] + cell[y[1]] == 4:
                    score[x] += SCORE_22
        else:
            score[x] = -1
    return score.index(max(score)) + 1


# 主函数
def main():
    # 窗口大小
    frame = np.zeros((600, 600, 3), np.uint8)
    # 按钮正常状态
    out_n = cv2.imread('out.png', cv2.IMREAD_COLOR)
    down_n = cv2.imread('down.png', cv2.IMREAD_COLOR)
    over_n = cv2.imread('over.png', cv2.IMREAD_COLOR)
    # 按钮X玩家按过
    out_x = cv2.imread('out_x.png', cv2.IMREAD_COLOR)
    down_x = cv2.imread('down_x.png', cv2.IMREAD_COLOR)
    over_x = cv2.imread('over_x.png', cv2.IMREAD_COLOR)
    # 按钮O玩家按过
    out_o = cv2.imread('out_o.png', cv2.IMREAD_COLOR)
    down_o = cv2.imread('down_o.png', cv2.IMREAD_COLOR)
    over_o = cv2.imread('over_o.png', cv2.IMREAD_COLOR)

    # 将按钮素材记为列表方便调用
    image_n = [out_n, over_n, down_n]
    image_x = [out_x, over_x, down_x]
    image_o = [out_o, over_o, down_o]

    buttonImage = [image_n, image_n, image_n,
                   image_n, image_n, image_n,
                   image_n, image_n, image_n]

    # cvui初始化
    cvui.init(WINDOWS_TITLE)

    # 各种参数声明
    Init()
    winFlag = 0
    drawFlag = 0
    errorInfo = ""
    target = 0
    resultInfo = ""
    step = 0
    player = 1

    while True:
        # 主窗口颜色
        frame[:] = (0, 0, 0)
        # 按钮位置绘图
        cvui.image(frame, 100, 100, buttonImage[0][0], buttonImage[0][1], buttonImage[0][2])
        cvui.image(frame, 100, 250, buttonImage[1][0], buttonImage[1][1], buttonImage[1][2])
        cvui.image(frame, 100, 400, buttonImage[2][0], buttonImage[2][1], buttonImage[2][2])
        cvui.image(frame, 250, 100, buttonImage[3][0], buttonImage[3][1], buttonImage[3][2])
        cvui.image(frame, 250, 250, buttonImage[4][0], buttonImage[4][1], buttonImage[4][2])
        cvui.image(frame, 250, 400, buttonImage[5][0], buttonImage[5][1], buttonImage[5][2])
        cvui.image(frame, 400, 100, buttonImage[6][0], buttonImage[6][1], buttonImage[6][2])
        cvui.image(frame, 400, 250, buttonImage[7][0], buttonImage[7][1], buttonImage[7][2])
        cvui.image(frame, 400, 400, buttonImage[8][0], buttonImage[8][1], buttonImage[8][2])

        player = step % 2 + 1

        if (firstHand and (player == 1)) or ((not firstHand) and (player == 2)):
            # 按钮绘图并接收反馈
            if cvui.button(frame, 100, 100, buttonImage[0][0], buttonImage[0][1], buttonImage[0][2]):
                target = 1
            elif cvui.button(frame, 100, 250, buttonImage[1][0], buttonImage[1][1], buttonImage[1][2]):
                target = 2
            elif cvui.button(frame, 100, 400, buttonImage[2][0], buttonImage[2][1], buttonImage[2][2]):
                target = 3
            elif cvui.button(frame, 250, 100, buttonImage[3][0], buttonImage[3][1], buttonImage[3][2]):
                target = 4
            elif cvui.button(frame, 250, 250, buttonImage[4][0], buttonImage[4][1], buttonImage[4][2]):
                target = 5
            elif cvui.button(frame, 250, 400, buttonImage[5][0], buttonImage[5][1], buttonImage[5][2]):
                target = 6
            elif cvui.button(frame, 400, 100, buttonImage[6][0], buttonImage[6][1], buttonImage[6][2]):
                target = 7
            elif cvui.button(frame, 400, 250, buttonImage[7][0], buttonImage[7][1], buttonImage[7][2]):
                target = 8
            elif cvui.button(frame, 400, 400, buttonImage[8][0], buttonImage[8][1], buttonImage[8][2]):
                target = 9
            else:
                target = 0
        elif (firstHand and (player == 2)) or ((not firstHand) and (player == 1)):
            target = CalculatingScore()
        else:
            target = 0

        # 文字提示
        cvui.text(frame, 40, 40, resultInfo, 0.45, 0x00ff00)
        cvui.text(frame, 40, 40, errorInfo, 0.45, 0xff0000)
        cvui.text(frame, 40, 60, "Press Esc to exit the game.", 0.45, 0x0000ff)

        if not (winFlag or drawFlag):

            # 文字提示
            cvui.text(frame, 40, 80, "Player{0}, Select a target!".format(player), 0.45, 0xffffff)
            # 确定玩家

            if target:
                if cell[target - 1] == 0:
                    if player == 1:
                        cell[target - 1] = 1
                    else:
                        cell[target - 1] = 2
                    step += 1
                    errorInfo = ""
                    target = 0
                else:
                    errorInfo = "There is already a pawn here! "

            for x in range(0, 9):
                if cell[x] == 1:
                    buttonImage[x] = image_x
                if cell[x] == 2:
                    buttonImage[x] = image_o

            winFlag = WinCheck()
            drawFlag = DrawCheck()

            if winFlag:
                resultInfo = "Player{0} win!".format(player)
            elif drawFlag:
                resultInfo = "Draw!"
            else:
                resultInfo = ""

        cvui.update()
        cvui.imshow(WINDOWS_TITLE, frame)
        if cv2.waitKey(20) == 27:
            break


if __name__ == "__main__":
    main()
